<?php

namespace App\Service;
use Hyperf\DbConnection\Db;
use Hyperf\Utils\ApplicationContext;
class DyPayService
{
//    protected $sp_appid = '';//服务商APPID（目前只有公众号）
//    protected $sp_mchid = '';//服务商商户号

    protected $appid = '';//小程序APPID
    protected $mchid = '';//商户号
    protected $apiV3Key = '';//支付秘钥（服务商V3级别）
    protected $privateKeyPath = '';//证书物理路径（私钥）
    protected $serialNo = '';//证书序列号
    protected $app_secret = '';//小程序通信秘钥
    protected $notify_url = '';//支付回调地址

//    #[Inject]
    public function __construct()
    {
        $container = ApplicationContext::getContainer();
        $this->redis = $container->get(\Hyperf\Redis\Redis::class);
    }

    public function getOrderSign($data,$app_id) {
        $privateUrl = "/home/wwwroot/ml_api/dy/20000/private_key.pem";
        $privateKeyStr = file_get_contents($privateUrl);
        $keyVersion = 2;
        $appId = $app_id;
        $method = 'POST';
        $url = "/requestOrder";
        $timestamp = time();
        $nonceStr = $this->randStr(10);
        $sign = $this->getByteAuthorization($privateKeyStr, $data, $appId, $nonceStr, $timestamp, $keyVersion,$url);
        return $sign;
    }
    public function getByteAuthorization($privateKeyStr, $data, $appId, $nonceStr, $timestamp, $keyVersion,$url) {
        $byteAuthorization = '';
        // 读取私钥
        $privateKey = openssl_pkey_get_private($privateKeyStr);
        if (!$privateKey) {
//            throw new InvalidArgumentException("Invalid private key");
            var_dump(1);
        } else {
            var_dump(2);
        }
        // 生成签名
        $signature = $this->getSignature("POST", $url, $timestamp, $nonceStr, $data, $privateKey);
        if ($signature === false) {
            return null;
        }
        // 构造 byteAuthorization
        $byteAuthorization = sprintf("SHA256-RSA2048 appid=%s,nonce_str=%s,timestamp=%s,key_version=%s,signature=%s", $appId, $nonceStr, $timestamp, $keyVersion, $signature);
        return $byteAuthorization;
    }

    public function getSignature($method, $url, $timestamp, $nonce, $data, $privateKey) {
        $targetStr = $method. "\n" . $url. "\n" . $timestamp. "\n" . $nonce. "\n" . $data. "\n";
        openssl_sign($targetStr, $sign, $privateKey, OPENSSL_ALGO_SHA256);
        $sign = base64_encode($sign);
        return $sign;
    }

    public function randStr($length = 8) {
        $chars = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789';
        $str = '';
        for ($i = 0; $i < $length; $i++) {
            $str .= $chars[mt_rand(0, strlen($chars) - 1)];
        }
        return $str;
    }





    public function get_applet_id($order_id)
    {
        $res = Db::table('data_payment')->select('applet_id')->where('order_id', $order_id)->first();
        return $res;
    }

    public function get_applet(string $applet_id)
    {
        # 获取小程序基本配置
        $redis_key = "applet:config";
        $applet_info = $this->redis->hGet($redis_key, $applet_id);
        $applet_info = json_decode($applet_info, true);
        if (empty($applet_info)) {
            # 获取小程序基本信息
            $applet_info = Db::table("applet")->where([
                "id" => $applet_id
            ])->first();
            $applet_info = $this->object_to_find_array($applet_info);
            $this->redis->hSet($redis_key, $applet_id, json_encode($applet_info));
        }
        return $applet_info;
    }

    public function ttpay($data)
    {
        $applet = $this->get_applet($data['applet_id']);
        $SALT = $applet['SALT'];
        var_dump($SALT);
        $url = 'https://developer.toutiao.com/api/apps/ecpay/v1/create_order';
        $params['app_id'] = $applet['app_id'];
        $params['out_order_no'] = (string)$data['order_id'];
        $params['total_amount'] = (int)$data['amount'];
        $params['subject'] = '短剧充值';
        $params['body'] = '短剧充值';
        $params['notify_url'] = 'https://kydy.kuaiyingbox.com/dy_pay/check_signature';
        $params['valid_time'] = 3600;

        $params['sign'] = $this->ttsign($params, $SALT);

        $http = $this->httpPost($url, $params);
        return json_decode($http, true);
    }

    public function ttsign($params, $SALT)
    {
        $rList = array();
        foreach ($params as $k => $v) {
            if ($k == "other_settle_params" || $k == "app_id" || $k == "sign" || $k == "thirdparty_id")
                continue;
            $value = trim(strval($v));
            $len = strlen($value);
            if ($len > 1 && substr($value, 0, 1) == "\"" && substr($value, $len, $len - 1) == "\"")
                $value = substr($value, 1, $len - 1);
            $value = trim($value);
            if ($value == "" || $value == "null")
                continue;
            array_push($rList, $value);
        }
        array_push($rList, "$SALT");
        sort($rList, 2);
        return md5(implode('&', $rList));
    }

    public function httpPost($url, $data = null)
    {
        $curl = curl_init();
        curl_setopt($curl, CURLOPT_URL, $url);
        curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);
        curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, false);
        if (!$data) return false;
        if (is_array($data)) {
            $data = json_encode($data);
        }
        curl_setopt($curl, CURLOPT_POST, 1);
        curl_setopt($curl, CURLOPT_POSTFIELDS, $data);
        curl_setopt($curl, CURLOPT_HEADER, 0);
        curl_setopt($curl, CURLOPT_HTTPHEADER, array(
            'Content-Type: application/json; charset=utf-8',
            'Content-Length:' . strlen($data),
            'Cache-Control: no-cache',
            'Pragma: no-cache'
        ));
        curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
        $res = curl_exec($curl);
        curl_close($curl);
        return $res;
    }
}